package app

import (
	"context"
	"os"
	"os/signal"
	"syscall"
	"time"
)

type DanLanApp struct {
	app   Application
	signs chan os.Signal
}

func NewDanLanApp(app Application) *DanLanApp {
	signs := make(chan os.Signal, 1)
	// syscall.SIGINT   代表用户键入ctrl+c时
	// syscall.SIGTERM  代表用户kill（docker stop时，会默认给docker内的1号进程发送syscall.SIGTERM）
	// syscall.SIGQUIT  代表用户键入退出字符，ctrl+
	// syscall.SIGKILL  代表用户kill -9
	signal.Notify(signs, syscall.SIGINT, syscall.SIGTERM, syscall.SIGQUIT)

	return &DanLanApp{
		app:   app,
		signs: signs,
	}
}

func (s *DanLanApp) Start() {
	// 启动异步去执行
	go s.app.Start()

	<-s.signs

	ctx, cancel := context.WithTimeout(context.Background(), 2*time.Second)
	defer cancel()
	s.app.Stop(ctx)
}

type Application interface {
	// Start 程序启动入口，可以是cronjob、httpserver、consumer...
	Start()
	// Stop 用于优雅关闭
	Stop(ctx context.Context)
}
